package com.gmadmin.service.auth;


import com.gmadmin.common.HttpStatus;
import com.gmadmin.exception.UserException;
import com.gmadmin.entity.vo.menu.SysMenuVo;
import com.gmadmin.entity.vo.role.SysRoleVo;
import com.gmadmin.entity.vo.user.SysUserVo;
import com.gmadmin.entity.vo.user.UserPrincipal;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.stereotype.Service;
import com.gmadmin.service.SysUserService;
import com.gmadmin.service.SysRoleService;
import com.gmadmin.service.SysMenuService;


import java.util.List;
import java.util.Objects;
import java.util.Set;
import java.util.stream.Collectors;

/**
 * @author zhangliang
 * @version 1.0
 * @date 2021/2/2 14:55
 */
@Service
public class CustomUserDetailsService implements UserDetailsService {
    private final SysUserService SysUserService;
    private final SysRoleService SysRoleService;
    private final SysMenuService ISysMenuService;
    protected Logger logger = LoggerFactory.getLogger(CustomUserDetailsService.class);

    public CustomUserDetailsService(SysUserService sysUserService, SysRoleService sysRoleService, SysMenuService iSysMenuService) {
        this.SysUserService = sysUserService;
        this.SysRoleService = sysRoleService;
        this.ISysMenuService = iSysMenuService;
    }

    @Override
    public UserDetails loadUserByUsername(String usernameOrEmailOrPhone) {
        UserDetails userDetails;
        SysUserVo sysUserVo = SysUserService.findByUsernameOrEmailOrPhone(usernameOrEmailOrPhone);
        if (Objects.nonNull(sysUserVo.getId())) {
            if (!sysUserVo.getEnabled().isEmpty()) {
                switch (sysUserVo.getEnabled()) {
                    case "0":
                        throw new UserException(HttpStatus.USER_STATUE_DISABLE);
                    case "2":
                        throw new UserException(HttpStatus.USER_STATUE_LOCKED);
                    case "4":
                        throw new UserException(HttpStatus.USER_STATUE_CANCELLATION);
                }
            }
            List<SysRoleVo> roles = SysRoleService.selectByUserId(sysUserVo.getId());
            if (Objects.nonNull(roles) && !roles.isEmpty()) {
                Set<Long> rolesId = roles.stream().map(SysRoleVo::getId).collect(Collectors.toSet());
                List<SysMenuVo> menus = ISysMenuService.findByRoleIdList(rolesId);
                userDetails = UserPrincipal.create(sysUserVo, roles, menus);
            } else {
                throw new UserException(HttpStatus.USER_ROLES_NOT_FOUND);
            }
        } else {
            throw new UserException(HttpStatus.USER_NOT_FOUND);
        }
        return userDetails;
    }


}
